﻿using System;
using LinkPad.Shapes;
using Windows.Foundation;
using Windows.UI;
using Windows.UI.Text;
using Windows.UI.Xaml;
using Windows.UI.Xaml.Controls;
using Windows.UI.Xaml.Documents;
using Windows.UI.Xaml.Input;
using Windows.UI.Xaml.Media;

namespace LinkPad.Handlers
{
    public class TextCreator : CanvasActionHandler, IHasFont
    {
        #region Fields

        private Color _textColor = Colors.Black;
        private readonly Color _defaultFillColor = Colors.Yellow;

        private bool _activated;

        #endregion

        #region Constructors

        public TextCreator(ShapeManager shapeManager)
            : base(shapeManager)
        {
            FontSize = ManagedText.DefaultFontSize;
            shapeManager.SetTextCreator(this);
        }

        #endregion

        #region Properties

        #region CanvasActionHander members

        public override Color MainColor
        {
            get
            {
                return _textColor;
            }
            set
            {
                _textColor = value;
            }
        }

        #endregion

        #region IHasEditor members

        public bool HasFont { get { return true; } }

        public double FontSize { get; set; }

        #endregion

        #endregion

        #region Methods

        public override void Activate()
        {
            _activated = true;
            base.Activate();
        }

        public override void Deactivate()
        {
            _activated = false;
            base.Deactivate();
        }

        /// <summary>
        ///  Edits the specific text block
        /// </summary>
        /// <param name="textBlock">The text block whose contents are to be changed</param>
        /// <param name="position">The position of the edit box to pop up</param>
        private void EditTextBlock(RichTextBlock textBlock, Point position)
        {
            var editBox = new RichEditBox
                              {
                                  BorderBrush = new SolidColorBrush(Colors.Red),
                                  Width = Math.Max(MyCanvas.ActualWidth*0.5, 100),
                                  Height = Math.Max(MyCanvas.ActualHeight*0.272, 100)
                              };

            editBox.SetValue(Canvas.LeftProperty, position.X);
            editBox.SetValue(Canvas.TopProperty, position.Y);

            editBox.Document.SetText(TextSetOptions.Unhide, "");

            if (textBlock.Blocks.Count > 0)
            {
                var p = (Paragraph)textBlock.Blocks[0];
                if (p.Inlines.Count > 0)
                {
                    var run = (Run)p.Inlines[0];
                    editBox.Document.SetText(TextSetOptions.Unhide, run.Text);
                }
            }

            //editBox.Document.SetText(TextSetOptions.None, textBlock.Text);
            editBox.LostFocus += (sender1, eventArgs) => EditBoxValueEntered(editBox, textBlock);
            
            textBlock.Visibility = Visibility.Collapsed;

            MyCanvas.Children.Add(editBox);
            editBox.Focus(FocusState.Pointer);
        }

        /// <summary>
        ///  Called when user input has been entered to the edit box
        /// </summary>
        /// <param name="editBox">The edit box user inputs to</param>
        /// <param name="textBlock">The text block the edit box applies to</param>
        private void EditBoxValueEntered(RichEditBox editBox, RichTextBlock textBlock)
        {
            string text;
            editBox.Document.GetText(TextGetOptions.NoHidden, out text);
            
            var paragraph = new Paragraph();
            paragraph.Inlines.Add(new Run { Text=text });

            textBlock.Blocks.Clear();
            textBlock.Blocks.Add(paragraph);

            textBlock.Visibility = Visibility.Visible;
            MyCanvas.Children.Remove(editBox);
        }

        protected override void HandleCanvasDoubleTapped(object sender, DoubleTappedRoutedEventArgs e)
        {
            var position = e.GetPosition(MyCanvas);

            var textBox = new ManagedText(ShapeManager)
                              {
                                  Foreground = new SolidColorBrush(_textColor),
                                  Fill = new SolidColorBrush(_defaultFillColor),
                                  X = position.X,
                                  Y = position.Y, 
                                  FontSize = FontSize
                              };

            var paragraph = new Paragraph();
            paragraph.Inlines.Add(new Run{Text = "<empty text>"});
            textBox.InnerTextBlock.Blocks.Add(paragraph);

            AttachManagedText(textBox);

            EditTextBlock(textBox.InnerTextBlock, position);

            ShapeManager.AddShape(textBox);

            e.Handled = true;

            base.HandleCanvasDoubleTapped(sender, e);
        }

        public void AttachManagedText(ManagedText managedText)
        {
            managedText.InnerTextBlock.Tapped += (o, args) =>
            {
                if (!_activated) return;
                var pos = args.GetPosition(MyCanvas);
                EditTextBlock(managedText.InnerTextBlock, pos);
                managedText.FontSize = FontSize;    // update the font size
                managedText.Foreground = new SolidColorBrush(_textColor);   // update the font color
            };
        }

        #endregion
    }
}
